package com.iqi.onigao.module.player;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Set;
import java.util.concurrent.TimeUnit;

import com.iqi.onigao.App;
import com.iqi.onigao.config.cfg.LotteryShowCfg;
import com.iqi.onigao.constant.SessionConstant;
import com.iqi.onigao.thread.ThreadExecutor;
import com.iqi.onigao.util.RandomUtil;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.date.TimeInterval;
import cn.hutool.core.map.MapUtil;
import cn.hutool.log.Log;
import cn.hutool.log.LogFactory;
import net.IClient;
import si.client.CCenterChat;
import si.client.CFriend;
import si.client.CItem;
import si.client.CLottery;
import si.client.CQuest;
import si.client.CUser;
import si.client.CWarehouse;
import si.pod.CChatPOD;
import si.pod.FriendPOD;
import si.pod.ItemPOD;
import si.pod.PlayerPOD;
import si.pod.QuestPOD;

public class PlayerAI implements Runnable{
	
	static final Log log = LogFactory.get(PlayerAI.class);
	private IClient session;
	private String account;
	private PlayerPOD player;
	
	public PlayerAI(IClient session) {
		super();
		this.session = session;
		this.account = session.getAttr(SessionConstant.ACCOUNT);
		this.player =  session.getAttr(SessionConstant.PLAYER); 
		log.info("玩家[{}]登录",account);
		
		sendChat("/cmd openfunction");
	}

	
	
	TimeInterval timer = DateUtil.timer();
	@Override
	public void run() {
		ThreadExecutor.execute(session, ()-> {
			
			try {
				long interval = timer.interval();
				if (session.isConnected()) {
					boolean offline = false;
					Runnable exec = session.getAttr(SessionConstant.EXEC);
					if (exec == null) {
						int r = RandomUtil.randomInt(App.limit);
						boolean send = false;
						switch (r) {
						case 0:
							send = sendChat("Hi 我是机器人-" + account);
							break;
						case 1:
							// 提交一个任务
							send = commitQuest();
							break;
						case 2:
							// 刷新悬赏
							send = CQuest.refreshBounty(session);
							break;
						case 3:
							// 申请好友
							send = applyFriends();
							break;
						case 4:
							// 处理好友申请
							send = dealWithApply();
							break;
						case 5:
							// 完成一个任务
							send = finishQuest();
							break;
						case 6:
							// 添加
							int num = RandomUtil.randomInt(1, 10);
							String cmd = RandomUtil.randomEle(App.cmds);
							send = sendChat("/cmd "+cmd+" " + num);
							break;
						case 7:
							send = lottery();
							break;
						case 8:
							send = sendMail();
							break;
						case 9:
							send = addItem();
							break;
						case 10:
							send = sellItem();
							break;
						case App.limit - 1:
							// 下线
							offline = true;
//							CUser.logout(session);
							session.close();
							send = true;
							break;
						}
						if (!send) {
							send = CUser.ping(session);
						}
						if (interval > (App.EVENT_TIME * 1000) + 500) {
							log.info("玩家[{}] Event:{} Send:{} interval:{}",account,r,send,interval);
						}
					}else {
						exec.run();
						session.removeAttr(SessionConstant.EXEC);
					}
					
					// 没有下线继续执行AI
					if (!offline) {
						session.setAttr(SessionConstant.FUTURE, ThreadExecutor.scheduleAtFixedRate(this, App.EVENT_TIME, TimeUnit.SECONDS));
					}
				}
				timer.restart();
			} catch (Exception e) {
				log.error(e);
			}
		});
	}

	// 出售物品
	private boolean sellItem() {
		boolean bool = false;
		Map<Long, ItemPOD> items = session.getAttr(SessionConstant.ITEMS);
		if (MapUtil.isEmpty(items)) {
			return bool;
		}
		Set<Long> sellItems = RandomUtil.randomEleSet(items.keySet(),1);
		for (Long id : sellItems) {
			bool |= CItem.sellItem(session, id, items.get(id).getNum() > 1 ? RandomUtil.randomInt(1, items.get(id).getNum()) : 1);
			break;
		}
		return bool;
	}

	// 添加物品
	private boolean addItem() {
		boolean bool = false;
		Integer itemID = RandomUtil.randomEle(App.itemIds);
		if (bool) {
			bool |= sendChat("/cmd additem " +  itemID + " " + RandomUtil.randomInt(1, 10));
		}
		return bool;
	}


	private boolean sendMail() {
		StringBuffer sb = new StringBuffer();
		sb.append("/cmd sendmail 35010001 标题 内容");
		return sendChat(sb.toString());
	}


	private boolean lottery() {
		Set<Integer> ids = RandomUtil.randomEleSet(LotteryShowCfg.cacheCfgs.keySet(), 1);
		for (Integer id : ids) {
			LotteryShowCfg showCfg = LotteryShowCfg.cacheCfgs.get(id);
			int poolId = RandomUtil.randomInt(showCfg.getPool().length);
			return CLottery.lottery(session, id,showCfg.getPool()[poolId]);			
		}
		return false;
	}


	private boolean sendChat(String content) {
		return CCenterChat.sendChat(session, new CChatPOD(3, 1, null, content));
	}


	private boolean finishQuest() {
		// 随机完成一个任务
		Map<Integer, QuestPOD> quests = session.getAttr(SessionConstant.QUESTS);
		for (Entry<Integer, QuestPOD> e : quests.entrySet()) {
			if (e.getValue().getFinNum() < e.getValue().getTgtNum()) {
				
				String content = "/cmd SetQuestPay " + e.getKey();
				return CCenterChat.sendChat(session, new CChatPOD(3, 1, null, content));
			}
		}
		return false;
	}
	

	private boolean dealWithApply() {
		List<FriendPOD> friends = player.getFriends();
		List<Long> ids = new ArrayList<>();
		for (FriendPOD friendPOD : friends) {
			if (friendPOD.getType() == 2 && RandomUtil.randomBoolean()) {
				ids.add(friendPOD.getId());
			}
		}
		// 处理好友申请
		if (CollUtil.isNotEmpty(ids)) {
			return CFriend.dealWithApply(session, ids, RandomUtil.randomBoolean());
		}
		return false;
	}


	private boolean commitQuest() {
		Map<Integer, QuestPOD> quests = session.getAttr(SessionConstant.QUESTS);
		for (Entry<Integer, QuestPOD> e : quests.entrySet()) {
			// 可以提交的任务
			if (e.getValue().getFinNum() >= e.getValue().getTgtNum()) {
				return CQuest.commitQuest(session, e.getKey());
			}
		}
		return false;
	}


	private boolean applyFriends() {
		// 取得推荐好友
		return CFriend.recommend(session);
	}
}
